/* 
 * File:   alspi.h
 * Author: aple
 */

#ifndef SPI_SW_HALL_H
#define SPI_SW_HALL_H

#include "mytype.h"

#ifdef __cplusplus
extern "C"
{
#endif

	typedef struct
	{
		uu8 speed;
		uu8 bits; //0-31 位数=bits+1
	} spi_info_type;

	/*****************************************************************************
    * @brief  SPI
    *****************************************************************************/
	typedef const struct
	{
		void (*cs_out_high)(void);
		void (*cs_out_low)(void);

		void (*sck_out_high)(void);
		void (*sck_out_low)(void);

		void (*mosi_out_high)(void);
		void (*mosi_out_low)(void);

		uu8 (*miso_st_get)(void); // 0/1

		void (*insert_clks)(void); //低速模式时时钟时钟宽度

		spi_info_type *info;
	} spi_cfg_type;

	void sw_spi_init(spi_cfg_type *spi);

	//MSB
	uu32 sw_spi_rw(spi_cfg_type *spi, uu32 wdata);
	//LSB
	uu32 sw_lsbspi_rw(spi_cfg_type *spi, uu32 wdata);

	void sw_spi_cs(spi_cfg_type *spi, uu8 cs);
	void sw_spi_speed(spi_cfg_type *spi, uu8 high1_or_low0);

	// 以下为简易接口MSB，内部不使用info 和 insert_clks
	uu8 sw_spi8_rw(spi_cfg_type *spi, uu8 wreg);
	void sw_spi8_write(spi_cfg_type *qpi, uu8 *wdata, uint16_t len);
	void sw_spi32_write(spi_cfg_type *qpi, uu32 *wdata, uint16_t len);
	void sw_spi8_read(spi_cfg_type *spi, uu8 *rdata, uint16_t len);
	void sw_spi32_read(spi_cfg_type *spi, uu32 *rdata, uint16_t len);

	uu8 sw_spi8_rw_lsb(spi_cfg_type *spi, uu8 wreg);
	void sw_spi8_write_lsb(spi_cfg_type *qpi, uu8 *wdata, uint16_t len);
	void sw_spi32_write_lsb(spi_cfg_type *qpi, uu32 *wdata, uint16_t len);
	void sw_spi8_read_lsb(spi_cfg_type *spi, uu8 *rdata, uint16_t len);
	void sw_spi32_read_lsb(spi_cfg_type *spi, uu32 *rdata, uint16_t len);
	
	// auto clks 1-32
	uu32 sw_spi_clks_rw(spi_cfg_type *spi, uu32 wreg, uu8 sclks);
	void sw_spi_clks_write(spi_cfg_type *spi, uu32 wreg, uu8 sclks);
	uu32 sw_spi_clks_read(spi_cfg_type *spi, uu8 sclks);
	
	uu32 sw_spi_clks_rw_lsb(spi_cfg_type *spi, uu32 wreg, uu8 sclks);
	void sw_spi_clks_write_lsb(spi_cfg_type *spi, uu32 wreg, uu8 sclks);
	uu32 sw_spi_clks_read_lsb(spi_cfg_type *spi, uu8 sclks);
	
	/*****************************************************************************
	* @brief  qpi-高位在前
	*****************************************************************************/
	typedef const struct
	{
		void (*cs_out)(char cs);

		void (*sck_out_high)(void); //从机采样边沿
		void (*sck_out_low)(void);

		void (*io_out)(uu32 qio); // 需要低速时外部加NOP
		uu32 (*io_in)(void);	  // 返回值[31:4]保持为0

	} qpi_cfg_type;

	// 以下为简易接口MSB，内部不使用info 和 insert_clks
	void sw_qpi8_write(qpi_cfg_type *qpi, uu8 *wdata, uint16_t len);
	void sw_qpi32_write(qpi_cfg_type *qpi, uu32 *wdata, uint16_t len);
	void sw_qpi8_read(qpi_cfg_type *qpi, uu8 *rdata, uint16_t len);
	void sw_qpi32_read(qpi_cfg_type *qpi, uu32 *rdata, uint16_t len);
	
	void sw_qpi8_write_lsb(qpi_cfg_type *qpi, uu8 *wdata, uint16_t len);
	void sw_qpi32_write_lsb(qpi_cfg_type *qpi, uu32 *wdata, uint16_t len);
	void sw_qpi8_read_lsb(qpi_cfg_type *qpi, uu8 *rdata, uint16_t len);
	void sw_qpi32_read_lsb(qpi_cfg_type *qpi, uu32 *rdata, uint16_t len);
	
#ifdef __cplusplus
}
#endif

#endif /* SPI_SW_HALL_H */
